package com.cjy.drools.drt;

import com.cjy.drools.pojo.Person;
import org.drools.template.ObjectDataCompiler;
import org.junit.Test;
import org.kie.api.KieServices;
import org.kie.api.io.ResourceType;
import org.kie.api.runtime.KieContainer;
import org.kie.api.runtime.KieSession;
import org.kie.internal.io.ResourceFactory;
import org.kie.internal.utils.KieHelper;

import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Collection;

/**
 * 规则引擎中，Drools提供了一个规则模板的概念，规则模板是指规则条件比较值是可变的，且可生成多个规则进行规则调用。规则模板可以分为两种：官方提到的以drt扩展名+xls（源数据）的方式和API模板赋值方式。
 * 第一种：官方提供的例子，通过规则模板drt文件+模板数据源xls文件，创建一个ExampleCheese.xls文件，目录为rulesTwo/isDrt，其内容如图10-20所示。
 *
 * @author cjy
 * @create 2020-04-01
 */
public class RulesDRT {

    @Test
    public void testIsDrt() {
        KieServices kss = KieServices.Factory.get();
        KieContainer kc = kss.getKieClasspathContainer();
        KieSession ks = kc.newKieSession("isDrt");

        Person person = new Person();
        person.setName("张三");
        person.setAge(40);
        ks.insert(person);

        int count = ks.fireAllRules();
        System.out.println("总得执行了" + count + "规则");
        System.out.println("总得执行了" + person.getClassName() + "规则");
        ks.dispose();

    }

    /**
     * 第二种方式 对代码的封装
     * 通过这种API的方式，可以对代码进行一个封装。
     * ObjectDataCompiler：调用规则模板的一个工具类。
     * Collection<Person> cfl：指给规则模板赋值的参数，一个元素就代表一个规则。
     * ResourceFactory：加载规则模板文件。
     * converter.compile(cfl, dis)：把规则文件与参数合并，生成drl文件
     */
    @Test
    public void testIsDRTapi() {
        // 调用规则模板的一个工具类
        ObjectDataCompiler converter = new ObjectDataCompiler();

        // 赋值给模板属性
        Person p = new Person();
        p.setAge(50);
        p.setClassName("一班");

        // 指给规则模板赋值的参数，一个元素代表一个规则，
        Collection<Person> cf1 = new ArrayList<Person>();
        cf1.add(p); // 每add一次，就代表一条规则

        InputStream in = null;

        try {
            // ResourceFactory加载规则模板文件
            in = ResourceFactory.newClassPathResource("rules/isDrt/Cheese.drt", RulesDRT.class).getInputStream();
        } catch (IOException e) {
            e.printStackTrace();
        }

        // 把规则文件与参数合并，生成drl文件
        String drl = converter.compile(cf1, in);
        System.out.println(drl);

        KieHelper helper = new KieHelper();
        helper.addContent(drl, ResourceType.DRL);

        KieSession kieSession = helper.build().newKieSession();

        Person person = new Person();
        person.setAge(50);
        person.setName("张三");
        kieSession.insert(person);

        int i = kieSession.fireAllRules();

        System.out.println(p.getClassName() + "总执行规则书：" + i);
        kieSession.dispose();
    }

}
